﻿package
{
	/* TODO: Need to do real-time pitch shift on spinner's sound, since they drop at random rates. */

	import flash.events.Event;
	import flash.events.SampleDataEvent;
	import flash.media.Sound;
	import flash.media.SoundChannel;
	import flash.trace.Trace;
	
	import org.flixel.FlxSprite;
	import org.flixel.FlxG;

	import ASF;
	
//	import org.sfxr.SfxrSynth;
	
	import Delay;
	
	import StateGameLoop;
	
	public class ASSpinner extends FlxSprite
	{
		//[Embed(source = 'data/spinner_drop_loop.mp3')] public var sndSlide:Class;
		
		public const q:Number = ((2 * Math.PI) / 44100);
		public var _parentState:StateGameLoop;
		private var sndSine:Sound;
		private var sndSineChannel:SoundChannel;
		private var sinePreviousY:Number = 0;
		/*----------------------------------------------*/
		public function ASSpinner(ParentState:StateGameLoop)
		{
			super(0, 0);
			_parentState = ParentState;
			
			sndSine = new Sound();
			sndSine.addEventListener(SampleDataEvent.SAMPLE_DATA, sineWaveGenerator);
			
			init();
		}
		
		/*----------------------------------------------*/
		private function init():void
		{
			exists = false;
			visible = false;
			if (sndSineChannel) {
				sndSineChannel.stop();
			}
			
		}
		
		/*----------------------------------------------*/
		public function sineWaveGenerator(event:SampleDataEvent):void
		{
			var c:uint = 0;
			var yoff:Number = sinePreviousY;
			var yinc:Number = (y - yoff) / 8192;
			var f:Number;
			var samp:Number;
	
			var _yoff_start:Number = yoff;
			
			var _f_start:Number =Number(2600 / ASF.GROUND_LEVEL) *
						Number( ( ASF.GROUND_LEVEL - Math.floor(yoff) ));
			
			for (c = 0; c < 8192; c++)
			{
				f = Number(2600 / ASF.GROUND_LEVEL) *
						Number( ( ASF.GROUND_LEVEL - Math.floor(yoff) ) );
				
				samp = Math.sin( ((c + event.position) * q) * f );
				
				// TODO: It'd be nice to have spinner position represented by l/r volume
				event.data.writeFloat(samp * 0.25);
				event.data.writeFloat(samp * 0.25);
				
				yoff += yinc;
			}
			
			var _f_stop:Number =Number(2600 / ASF.GROUND_LEVEL) *
						Number( ( ASF.GROUND_LEVEL - Math.floor(yoff) ) );
			sinePreviousY = y;
			//trace("start = " + _yoff_start + " end = " + yoff + " y = " + y);
			//trace("f_start = " + _f_start + " end = " + _f_stop + " yinc = " + yinc + " y = " + y);
			
			
		}
		/*----------------------------------------------*/
		public function spawn():void
		{
			x = FlxG.random() * (FlxG.width - width);
			y = -height;
			sinePreviousY = -height;

			velocity.y = ASF.MIN_SPINNER_DROP_SPEED + (FlxG.random() * ASF.MAX_SPINNER_DROP_SPEED);

			visible = true;
			exists = true;
			sndSineChannel = sndSine.play();
		}
		
		/*----------------------------------------------*/
		override public function update():void
		{
			if (y >= ASF.GROUND_LEVEL) {
				init();
				_parentState.playerKilled();
			}
						
			// Sometimes they trail off the screen due to horizontal velocity
			if (!onScreen()) {
				init();
			}
			super.update();
		}
		
		
		/*----------------------------------------------*/
		override public function hurt(Damage:Number):void
		{
			init();
		}
		
		/*----------------------------------------------*/
		public function getScore():int
		{
			return 0;
		}
	}
	
}